//Antonov Vitaliy 013 group

import java.awt.Desktop;
import java.io.BufferedReader;
import java.io.BufferedWriter;
import java.io.File;
import java.io.FileWriter;
import java.io.IOException;
import java.io.InputStreamReader;
import java.text.DateFormat;
import java.text.SimpleDateFormat;
import java.util.Date;
import java.util.Scanner;
import java.util.Vector;
import java.util.regex.Pattern;

public class FileManager
{
	public static void main(String[] args)
	{
		//This is main function.
		//In the infinitive loop we read input lines and analyze them.
		current_file = new File(System.getProperty("user.dir"));
		BufferedReader bReader = new BufferedReader (new InputStreamReader(System.in)); 
		while (true)
		{
			try 
			{
				String str = bReader.readLine();
				if (str == null)
					return;
				if (str.startsWith("ls"))
					ls_command(str);
				else if (str.startsWith("cd"))
					cd_command(str);
				else if (str.startsWith("open"))
					open_command(str);
				else if (str.startsWith("edit"))
					edit_command(str);
				else if (str.startsWith("touch"))
					touch_command(str);
				else if (str.startsWith("mkdir"))
					mkdir_command(str);
				else if (str.startsWith("exit"))
					return;
				else
					System.out.println("\nAvailable commands: ls, cd, open, edit, touch, mkdir, exit\n");
			} 
			catch (IOException e) 
			{
				e.printStackTrace();
			}
		}
	}
	
	//This function gets string with spaces and commands like "edit 1.txt"
	//and returns the vector with each parameter (in our example it'll be {edit}, {1.txt} - vector.
	public static Vector<String> get_args(String str0)
	{
		Pattern p = Pattern.compile(" +");
		Pattern p2 = Pattern.compile("[^ ]+");
		Scanner scan = new Scanner(str0);
		scan.useDelimiter(p);
		
		Vector<String> args = new Vector<String>();
		String temp = scan.next(p2);
		args.add(temp);
		
		if (scan.hasNext(p2))
		{
			String temp2 = scan.next(p2);
			temp = str0.substring(str0.indexOf(temp2));
			args.add(temp);
		}

		return (args);
	}
	
	public static void ls_command(String str0)
	{
		//Get arguments and check them.
		Vector<String> args = get_args(str0);
		
		if (!args.get(0).equals("ls"))
		{
			System.out.println("\nAvailable commands: ls, cd, open, edit, touch, mkdir, exit\n");
			return;
		}
		
		if (args.size() > 1)
		{
			if (args.get(1).equals("help"))
			{
				System.out.println("Usage: ls [help]");
				System.out.println("This programm shows information about all files and directories in"+
									"\ncurrent directory: date of last modification, size (in case it\'s file) or DIR, name");
				System.out.println("[help] shows this help information");
				return;
			}
			else
			{
				System.out.println("Type \"ls help\" for describing usage of ls");
				return;
			}
		}
		
		//Look through all files and directories in current directory and print information about them.
		System.out.println("In "+current_file.getAbsolutePath()+"\n");
		String[] content = current_file.list();
		for (String str: content)
		{
			String to_print;
			File file = new File (current_file.getPath(), str);
			DateFormat date = new SimpleDateFormat("dd.MM.yyyy HH:mm:ss");
			
			if (file.isDirectory())
				to_print = "DIR";
			else
				to_print = ""+file.length();
			
			System.out.format("%s  %10s   %s\n", date.format(new Date(file.lastModified())), to_print, file.getName());
		}
	}
	
	public static void cd_command(String str0)
	{
		//Get arguments and check them.
		Vector<String> args = get_args(str0);
		
		if (!args.get(0).equals("cd"))
		{
			System.out.println("\nAvailable commands: ls, cd, open, edit, touch, mkdir, exit\n");
			return;
		}
		
		if (args.size() != 2)
		{
			System.out.println("Type \"cd help\" for describing usage of cd");
			return;
		}

		if (args.get(1).equals("help"))
		{
			System.out.println("Usage: cd [help] | [DIR]");
			System.out.println("This programm changes current directory to stated");
			System.out.println("[help] shows this help information");
			System.out.println("[DIR] determines the directory to be opened.");
			System.out.println("It\'s allowed to use only \"/\" symbols as delimeters");
			return;
		}
		
		if (args.get(1).contains("\\"))
		{
			System.out.println("It\'s prohibited to use \"\\\" here. ");
			System.out.println("Type \"cd help\" for describing usage of cd");
			return;
		}
		
		//splitting our address and work with every part
		File cur_file = new File(current_file.getAbsolutePath());
		String [] sub_dir = args.get(1).split("/");
		for (int i = 0; i < sub_dir.length; i++)
		{
			if (i == 0 && sub_dir[i].equals(""))
				continue;
			
			if (i == 0 && sub_dir[i].contains(":"))
			{
				cur_file = new File(sub_dir[i]+File.separator);
				continue;
			}
			
			if (sub_dir[i].equals("."))
				continue;
				
			
			if (sub_dir[i].equals(".."))
			{
				if (cur_file.getParentFile() == null)
				{
					System.out.println("Directory not found");
					return;
				}
				cur_file = new File(cur_file.getParentFile().getAbsolutePath());
				continue;
			}
			
			cur_file = new File(cur_file, sub_dir[i]);
			if (!cur_file.exists() || (cur_file.exists() && cur_file.isFile()))
			{
				System.out.println("Directory not found");
				return;
			}
			
		}
		current_file = new File(cur_file.getAbsolutePath());
	}
	
	public static void open_command(String str0)
	{
		//Get arguments and check them.
		Vector<String> args = get_args(str0);
		
		if (!args.get(0).equals("open"))
		{
			System.out.println("\nAvailable commands: ls, cd, open, edit, touch, mkdir, exit\n");
			return;
		}
		
		if (args.size() != 2)
		{
			System.out.println("Type \"open help\" for describing usage of open");
			return;
		}
		
		
		if (args.get(1).equals("help"))
		{
			System.out.println("Usage: open [help] | [FILE]");
			System.out.println("This programm launches stated file by means of your OS");
			System.out.println("You can open files which are only in current directory");
			System.out.println("[help] shows this help information");
			System.out.println("[FILE] determines the file to be launched");
			return;
		}
		
		String[] content = current_file.list();
		boolean present = false;
		
		for (String str: content)
		{
			if (str.equals(args.get(1)))
			{
				present = true;
				break;
			}
		}
		
		if (present)
		{
			File temp_file = new File(current_file, args.get(1));
			Desktop desk = Desktop.getDesktop();
			if (temp_file.isFile())
			{
				try 
				{
					desk.open(temp_file);
				} 
				catch (IOException e) 
				{
					System.out.println("Can't open file");
				}
			}
			else
				System.out.println("Wrong name of file");
			return;
		}
	}
	
	public static void edit_command(String str0)
	{
		//Get arguments and check them.
		Vector<String> args = get_args(str0);
		
		if (!args.get(0).equals("edit"))
		{
			System.out.println("\nAvailable commands: ls, cd, open, edit, touch, mkdir, exit\n");
			return;
		}
		
		if (args.size() != 2)
		{
			System.out.println("Type \"edit help\" for describing usage of edit");
			return;
		}
		
		
		if (args.get(1).equals("help"))
		{
			System.out.println("Usage: edit [help] | [name_of_file]");
			System.out.println("This programm creates new file (or overwrite existing) and writes to it typed characters");
			System.out.println("To stop writing type \"$$$\" at the end of the line and press ENTER");
			System.out.println("\"$$$\" won\'t be included in the output file");
			System.out.println("[help] shows this help information");
			System.out.println("[name_of_file] determines the name of the new file to be created in current directory");
			return;
		}
		
		System.out.println("You chose writing mode");
		BufferedReader bReader = new BufferedReader (new InputStreamReader(System.in));
		String text = "";
		while (true)
		{
			try 
			{
				String str = bReader.readLine();
				if (str.endsWith("$$$"))
				{
					str = str.substring(0, str.length()-3);
					if (!str.equals(""))
					{
						text += System.getProperty("line.separator");
						text += str;
					}
					break;
				}
				else
				{
					if (text.equals(""))
						text = str;
					else
					{
						text += System.getProperty("line.separator");
						text += str;
					}
						
				}
			} 
			catch (IOException e) 
			{
				e.printStackTrace();
			}
		}
		
		File file = new File(args.get(1));
		
			try 
			{
				BufferedWriter out = new BufferedWriter(new FileWriter(file));
				out.write(text);
				out.close();
			} 
			catch (IOException e) 
			{
				e.printStackTrace();
			}

	}
	
	public static void touch_command(String str0)
	{
		//Get arguments and check them.
		Vector<String> args = get_args(str0);
		
		if (!args.get(0).equals("touch"))
		{
			System.out.println("\nAvailable commands: ls, cd, open, edit, touch, mkdir, exit\n");
			return;
		}
		
		if (args.size() != 2)
		{
			System.out.println("Type \"touch help\" for describing usage of touch");
			return;
		}
		
		
		if (args.get(1).equals("help"))
		{
			System.out.println("Usage: touch [help] | [name_of_file]");
			System.out.println("This programm creates empty file with stated name in the current directory");
			System.out.println("[help] shows this help information");
			System.out.println("[name_of_file] determines the name of the new file to be created in current directory");
			return;
		}
		
		File file = new File(args.get(1));
		try 
		{
			BufferedWriter out = new BufferedWriter(new FileWriter(file));
			out.write("");
			out.close();
		} 
		catch (IOException e) 
		{
			e.printStackTrace();
		}
	}
	
	public static void mkdir_command(String str0)
	{
		//Get arguments and check them.
		Vector<String> args = get_args(str0);
		
		if (!args.get(0).equals("mkdir"))
		{
			System.out.println("\nAvailable commands: ls, cd, open, edit, touch, mkdir, exit\n");
			return;
		}
		
		if (args.size() != 2)
		{
			System.out.println("Type \"mkdir help\" for describing usage of mkdir");
			return;
		}
		
		
		if (args.get(1).equals("help"))
		{
			System.out.println("Usage: mkdir [help] | [name_of_dir]");
			System.out.println("This programm creates empty directory with stated name in the current directory");
			System.out.println("[help] shows this help information");
			System.out.println("[name_of_dir] determines the name of the new directory to be created in current directory");
			return;
		}
		
		File file = new File(args.get(1));
		file.mkdir();
	}
	private static File current_file;
}
